import React, { Component } from 'react';
import PropTypes from "prop-types";
import { 
        View,
        Image,
        StyleSheet,
        FlatList,
        ActivityIndicator,
        Platform,
        Dimensions
    } from 'react-native';
import Label from '../label/index';
import RefreshStates from '../pullrefresh/RefreshStates';
import LoadStates from '../pullrefresh/LoadStates';
import Font from '../../config/theme/standard/fonts';
import Color from '../../config/theme/standard/color';

const ITEM_HEIGHT = 44;

export default class Table extends Component{
    constructor(props) {
        super(props);
        this.state = {     
            isShow: false,
        };
    }


    _keyExtractor = (item,index) => {
        return 'item-'+index;
    }

    _getColWidth = () => {
        let widthArr = [];
        for(let i=0; i < this.props.headData.length; i++){
            widthArr.push(this.props.headData[i].width)
        }
        return widthArr;
    }

    _renderItemDeltail = (values,color,styleCol,colDescStyle) => {
        color=color?color:Color.black
        styleCol=styleCol?styleCol:{}
        colDescStyle=colDescStyle?colDescStyle:{}
        let widthArr = this._getColWidth();
        let textAlign = this.props.alignment;
        let itemDetail=[];
        for(let i = 0; i< values.length; i++){
            if(Array.isArray(values[i]) && values[i].length > 1){
                itemDetail.push(
                    <View key={i} style={[styles.item,{flexDirection:'column',width:widthArr[i+1]}]}>
                        <Label text={values[i][0]+''}   numberOfLines={2}  labelStyle={[{color:color,fontSize:Font.table.itemFontSize,textAlign},styleCol]} />
                        <Label text={values[i][1]+''}   numberOfLines={2} labelStyle={[{color:Color.table.itemDescText,fontSize:Font.table.itemDescFontSize,textAlign},colDescStyle]} />
                    </View>
                );
            }else{
                itemDetail.push(
                    <View style={[styles.item,{width:widthArr[i+1]}]} key={i}>
                        <Label text={values[i]+''}  numberOfLines={2} labelStyle={[{color:color,fontSize:Font.formFontSize,textAlign},styleCol]} />
                    </View>
                );                
            }  
        }      
        return itemDetail;
    }

    _renderItem = (item) =>{
        let firstCol = item.item.name;
        let widthArr = this._getColWidth();
        let nameStyle=item.item.nameStyle?item.item.nameStyle:{}
        let bgColor = Color.table.itemBackground1;
        if(this.props.zebraLine){
            bgColor = item.index % 2 == 0 ? this.props.zebraLineColor : bgColor;
        }   
        let itemValueDetail = this._renderItemDeltail(item.item.value,item.item.color,item.item.colStyle,item.item.colDescStyle);
        let align
        if(this.props.firstColAlign == 'right') {
            align = 'flex-end'
        } else if (this.props.firstColAlign == 'left') {
            align = 'flex-start'
        } else {
            align = 'center'
        }
        if(!this.props.hasName){
            return (
                <View style={[styles.itemView,{backgroundColor:bgColor}]}>
                    {itemValueDetail}
                </View>
            )
        }else {
            if (!this.props.isImageHorizontal) {
            return (
                <View style={[styles.itemView, {backgroundColor: bgColor}]}>
                    <View style={[styles.item, styles.itemCol, {width: widthArr[0],minHeight:ITEM_HEIGHT,height:'100%'}]}  ref={(name)=>{this.firstCol=name}}>
                        <View style={{flexDirection:'row',justifyContent:align,alignItems:'center'}}>
                            {
                                item.item.icon ? (
                                    <Image source={item.item.icon} style={{width:15,height:10,marginRight:5}}/>
                                ) :null
                            }
                            {
                                item.item.iconDesc ? (
                                    <Label text={item.item.iconDesc}  labelStyle={item.item.iconDescStyle?item.item.iconDescStyle:{}}/>
                                ) : null
                            }
                        </View>
                        <Label text={firstCol} numberOfLines={2} labelStyle={[{textAlign:this.props.firstColAlign,fontSize: Font.formFontSize, color: Color.black},nameStyle]}/>
                    </View>
                    <View style={{flexDirection:'row'}}>
                        {itemValueDetail}
                    </View>
                </View>
            );
        }else {
            return (
                <View style={[styles.itemView, {backgroundColor: bgColor}]}>
                    <View style={[styles.item, styles.itemCol, {width: widthArr[0], minHeight: ITEM_HEIGHT, height: '100%'}]} ref={(name)=>{this.firstCol=name}}>
                        <View style={{flexDirection: 'row', justifyContent: align, alignItems: 'center'}}>
                            {
                                item.item.icon ? (
                                    <Image source={item.item.icon} style={{width: 16, height: 16, marginRight: 2}}/>
                                ) :null
                            }
                            <Label text={firstCol} numberOfLines={2} labelStyle={[{textAlign: this.props.firstColAlign, fontSize: Font.table.itemFontSize, color: Color.table.itemText}, nameStyle]}/>
                        </View>
                    </View>    
                    <View style={{flexDirection: 'row'}}>
                        {itemValueDetail}
                    </View>
                </View>
                );
           }       
        }
    }

    _renderHeader = () => {
        let widthArr = this._getColWidth(); 
        let textAlign = this.props.alignment;
        //headStyle
        let headStyles = this.props.headStyles;
        let headBg = Color.table.headerBackground;
        let headTextColor = Color.table.headerText;
        let headHeight = ITEM_HEIGHT;
        let headFontSize = Font.table.headerFontSize;
        if(headStyles){
            if(headStyles.backgroundColor){
                headBg = headStyles.backgroundColor;
            }
            if(headStyles.height){
                headHeight = headStyles.height;
            }
            if(headStyles.fontSize){
                headFontSize = headStyles.fontSize;
            }
            if(headStyles.color){
                headTextColor = headStyles.color;
            }
        }     
        let headArea = [];        
        for(let i =0; i < this.props.headData.length; i++){
                 
            if(i == 0){
                headArea.push(
                    <View key={i} style={[styles.item,{height: headHeight,width:widthArr[i]}]}>
                        <Label text={this.props.headData[i].name}  labelStyle={{color:headTextColor,fontSize:headFontSize,textAlign:this.props.firstColAlign}} />
                    </View>
                );
            }else{
                headArea.push(
                    <View key={i} style={[styles.item,{height: headHeight,width:widthArr[i]}]}>
                        <Label text={this.props.headData[i].name}  labelStyle={{color:headTextColor,fontSize:headFontSize,textAlign}} />
                    </View>
                );
            }
            
        }       
        return (
            <View style={[styles.itemView,{backgroundColor:headBg,height:headHeight,borderBottomColor:Color.table.border,borderBottomWidth:this.props.showLine ? 1 : 0}]}>
                {headArea}
            </View>
        );
    }

    _header = () => {
        let {headData, headFixed, refreshSucessInfo, refreshState,
        refreshFailtureInfo, refreshNoInternetInfo, refreshNoMoreInfo} = this.props;
        let {isShow} = this.state;
        
        if(isShow){
            if(refreshState == RefreshStates.Normal){
                return (
                    <View>
                        {headData && !headFixed ? this._renderHeader() : null}
                    </View>
                );
            }else if(refreshState == RefreshStates.RefreshSucess){
                return (
                    <View style={{flexDirection:'column'}}>
                        <View style={[styles.itemView,{justifyContent:'center',height:ITEM_HEIGHT}]}>
                            <Label text={refreshSucessInfo}  labelStyle={{marginLeft:20,fontSize:Font.table.loadingFontSize,color:Color.table.loadingText}} />
                        </View>
                        {headData && !headFixed ? this._renderHeader() : null}
                    </View>
                );
            }else{
                let info;
                if(refreshState == RefreshStates.RefreshFailure){
                    info = refreshFailtureInfo;
                }else if(refreshState == RefreshStates.NoRefreshing){
                    info = refreshNoMoreInfo;
                }else if(refreshState == RefreshStates.NoInternet){
                    info = refreshNoInternetInfo;
                }else{
                    return <View />
                }         
                return (
                    <View style={{flexDirection:'column'}}>
                        <View style={[styles.itemView,{justifyContent:'center',height:ITEM_HEIGHT}]}>                       
                            <Label text={info}  labelStyle={{marginLeft:20,fontSize:Font.table.loadingFontSize,color:Color.table.loadingText}} />
                        </View>
                        {headData && !headFixed ? this._renderHeader() : null}
                    </View>
                );         
            }
        }else{
            return (
                <View>
                    {headData && !headFixed ? this._renderHeader() : null}
                </View>
            );
        }       
    }

    //渲染加载图标
    _renderLoadingIcon = () => {
        if(this.props.loadingIcon){
            return (
                <Image source={this.props.loadingIcon} style={{width:28,height:28,resizeMode: 'contain'}}/>
            );
        }else{
            if(this.props.loadingDefaultIcon){
                return <ActivityIndicator />;
            }else{
                return null;
            }
        }
    }

    _renderFooter = () => {
        let {loadState, footerFixed, footer, loadingInfo, loadingNoMoreInfo,
            loadingFailtureInfo } = this.props;
        if(loadState == LoadStates.Finish){
            return (
                <View>
                    {footer && !footerFixed ? footer : null}
                </View>
            );
        }else if(loadState == LoadStates.Loading){
            return (
                <View style={{flexDirection:'column'}}>
                    <View style={[styles.itemView,{justifyContent:'center',height:ITEM_HEIGHT}]}>
                        {this._renderLoadingIcon()}
                        <Label text={loadingInfo}  labelStyle={{marginLeft:6,fontSize:Font.table.loadingFontSize,color:Color.table.loadingText}} />
                    </View>
                    {footer && !footerFixed ? footer : null}
                </View>
            );
        }else{
            let loadInfo;
            if(loadState == LoadStates.NoMoreData){
                loadInfo = loadingNoMoreInfo;
            }else if(loadState == LoadStates.LoadFailure){
                loadInfo = loadingFailtureInfo;
            }else{
                return <View />
            }
            return (
                <View style={{flexDirection:'column'}}>
                    <View style={[styles.itemView,{justifyContent:'center',height:ITEM_HEIGHT}]}>
                        <Label text={loadInfo}  labelStyle={{marginLeft:15,fontSize:Font.formFontSize}} />
                    </View>
                    {footer && !footerFixed ? footer : null}
                </View>
            );
        }
    }

    _separator = () => {
        if(this.props.showLine){
            return <View style={{height:1,backgroundColor:Color.table.border}}/>;
        }else{
            return <View style={{height:0,backgroundColor:Color.table.border}}></View>
        }      
    }

    _onLoadMore = () => {
      //若已无更多数据，则停止执行加载方法
      if (this.props.loadState == LoadStates.NoMoreData) {
        return;
      }
      if (this.props.onLoadMore) {
        //防止异步方法多次调用
        if (this.props.loadState == LoadStates.Loading) {
          return;
        } else {
          this.props.onLoadMore();
        }
      }
    };

    _onRefresh = () => {
        if(this.props.onRefresh){
            this.props.onRefresh();           
        }
    }

    static getDerivedStateFromProps(nextProps, prevState) {
        return null;
      }

    componentWillUnmount(){
        clearTimeout(this.timer);
    }   

    render() {
        let { headFixed, footerFixed, data ,tabHeight, footer, refreshState, border} = this.props;
        let tabBorder;
        if(border){
            tabBorder = {borderBottomWidth:1,borderTopWidth:1,borderColor:Color.table.border};
        }

        return (
            <View style={[tabBorder,{height:tabHeight}]}>
                {headFixed ? this._renderHeader() : <View />}
                <FlatList
                    ListHeaderComponent={this._header}
                    ListFooterComponent={this._renderFooter}
                    ItemSeparatorComponent={this._separator}
                    renderItem={this._renderItem}
                    data={data}
                    onRefresh={this._onRefresh}
                    refreshing={refreshState == 1 ? true:false}
                    keyExtractor={this._keyExtractor}
                    getItemLayout={(data,index)=>(
                        {length: ITEM_HEIGHT, offset: (ITEM_HEIGHT+2) * index, index}
                    )}
                    onEndReachedThreshold={Platform.OS =='ios' ? -0.1 : 0.1}
                    onEndReached={this._onLoadMore}
                    initialNumToRender={20}
                    >
                </FlatList>
                {footerFixed ? footer : <View />}
            </View>
        );
    }

}

Table.propTypes = {
    //表格数据
    data: PropTypes.array.isRequired,
    //表格构件所占用高度
    tabHeight: PropTypes.number,
    //表头数据
    headData: PropTypes.array.isRequired,
    //表头样式，包括背景颜色，字体颜色，高度，字体大小
    headStyles: PropTypes.object,
    //是否固定表头
    headFixed: PropTypes.bool,
    //列内容对齐方式，除第一列
    alignment: PropTypes.oneOf(['left','center','right']),
    //列内容对齐方式，第一列
    firstColAlign: PropTypes.oneOf(['left','center','right']),
    //是否显示分割线
    showLine: PropTypes.bool,
    //是否显示表格上下边框
    border: PropTypes.bool,
    //是否显示斑马线
    zebraLine: PropTypes.bool,
    //斑马线颜色
    zebraLineColor: PropTypes.string,
    //自定义底部内容
    footer: PropTypes.any,
    //是否固定底部内容
    footerFixed: PropTypes.bool,

    //下拉刷新状态
    refreshState: PropTypes.number,
    //下拉刷新回调函数
    onRefresh: PropTypes.func,
    //刷新成功提示语
    refreshSucessInfo : PropTypes.string,
    //刷新失败提示语
    refreshFailtureInfo: PropTypes.string,
    //暂无更新提示语
    refreshNoMoreInfo: PropTypes.string,
    //刷新无网络连接提示语
    refreshNoInternetInfo: PropTypes.string,

    //底部上拉加载状态
    loadState: PropTypes.number,
    //底部上拉加载更多回调函数
    onLoadMore: PropTypes.func,
    //底部正在加载提示语
    loadingInfo: PropTypes.string,
    //是否显示底部正在加载默认图标（菊花图标）
    loadingDefaultIcon: PropTypes.bool,
    //底部正在加载Icon
    loadingIcon: PropTypes.any,
    //底部无更多数据提示语
    loadingNoMoreInfo: PropTypes.string,
    //底部加载失败提示语
    loadingFailtureInfo: PropTypes.string,
    //table每一行数据是否有标题
    hasName:PropTypes.bool,
    //第一列图片和文字是否横向展示
    isImageHorizontal: PropTypes.bool
}

Table.defaultProps = {
    tabHeight: Dimensions.get('window').height,
    headFixed: false,
    alignment: 'right',
    firstColAlign:'center',
    showLine: false,
    border: false,
    zebraLine: false,
    zebraLineColor: Color.table.itemBackground2,
    footerFixed: false,
    headStyles:{
        color: Color.table.headText,
        backgroundColor: Color.table.headBackground
    },
    loadState: LoadStates.Finish,
    loadingInfo: '正在加载...',
    loadingNoMoreInfo: '没有更多了...',
    loadingFailtureInfo: '加载失败...',
    loadingDefaultIcon: true,

    refreshState: RefreshStates.Normal,
    refreshSucessInfo : '更新成功',
    refreshFailtureInfo: '更新出错，请稍后再试！',
    refreshNoMoreInfo: '暂无更新，请休息一会！',
    refreshNoInternetInfo: '网络连接失败，请稍后再试！',
    hasName:true,
    //第一列图片和文字是否横向展示
    isImageHorizontal: false, 
}

const styles = StyleSheet.create({
    itemView : {
        flexDirection:'row',
        justifyContent:'flex-start',
        alignItems:'center'
    },
    loadView : {
        flexDirection:'column',
    },
    itemCol:{
        justifyContent:'flex-start'
    },
    item: {
        justifyContent: 'flex-start',
        paddingHorizontal: 15,
        paddingTop: 12,
        paddingBottom: 12
    }
});

